#include <iostream>
#include <unistd.h>
#include <pthread.h>

int ticket = 0;
pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cond = PTHREAD_COND_INITIALIZER;

void *route(void *args)
{
    std::string name = static_cast<char *>(args);
    while (1)
    {
        pthread_mutex_lock(&mutex);
        if (ticket > 0)
        {
            usleep(1000);
            std::cout << name << " buys a new ticket: " << ticket << std::endl;
            ticket--;

            pthread_mutex_unlock(&mutex);
        }
        else
        {
            pthread_cond_wait(&cond, &mutex);
            std::cout << "主线程出票完成, " << name << " 醒来" << std::endl;
            
            pthread_mutex_unlock(&mutex);
        }
        // usleep(50);
    }
    return nullptr;
}

int main()
{
    pthread_t t1, t2, t3;
    pthread_create(&t1, nullptr, route, (void *)"thread 1");
    pthread_create(&t2, nullptr, route, (void *)"thread 2");
    pthread_create(&t3, nullptr, route, (void *)"thread 3");

    int cnt = 10;
    while(true)
    {
        sleep(5);
        ticket += cnt;
        std::cout << "主线程发票啦, ticket: " << ticket << std::endl;

        pthread_cond_signal(&cond);
        // pthread_cond_broadcast(&cond);
    }

    pthread_join(t1, nullptr);
    pthread_join(t2, nullptr);
    pthread_join(t3, nullptr);

    return 0;
}

// pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
// pthread_cond_t cond = PTHREAD_COND_INITIALIZER;

// void *active(void *args)
// {
//     std::string name = static_cast<char *>(args);

//     while (true)
//     {
//         pthread_mutex_lock(&mutex);

//         // 没有对资源释放就绪的判定
//         // std::cout << name << " is waiting" << std::endl;
//         pthread_cond_wait(&cond, &mutex); // mutex???
//         std::cout << name << " is active" << std::endl;

//         pthread_mutex_unlock(&mutex);
//     }
// }

// int main()
// {
//     pthread_t tid1, tid2, tid3;
//     pthread_create(&tid1, nullptr, active, (void *)"thread-1");
//     pthread_create(&tid2, nullptr, active, (void *)"thread-2");
//     pthread_create(&tid3, nullptr, active, (void *)"thread-3");

//     sleep(1);
//     std::cout << "main thread ctrl begin..." << std::endl;

//     while (true)
//     {
//         std::cout << "main wakeup thread..." << std::endl;
//         // pthread_cond_signal(&cond);
//         pthread_cond_broadcast(&cond);
//         sleep(1);
//     }

//     pthread_join(tid1, nullptr);
//     pthread_join(tid2, nullptr);
//     pthread_join(tid3, nullptr);

//     return 0;
// }